<script setup lang="ts">
import { ref, reactive, watch, nextTick } from 'vue'
import type { FormInstance } from 'ant-design-vue'
import { message } from 'ant-design-vue'
import useRoleList from './roleList'
import useRouteList from '@/views/sysAuth/route/routeList'
import useRequestList from '@/views/sysAuth/request/requestList'
import { user as useUser } from '@/store'
import { listToTree, traverseTreeArr,sortTreeArr} from '@/common/utils'
// import { layoutRouteName } from '@/router/config'
import GiveAuth from './giveAuth.vue'
import dayjs from 'dayjs'
import { useModalDraggable } from '@/hooks/useModalDraggable'
import {actionConfigMap,type actionKeyType} from "./roleList"

const columns: { [key: string]: any }[] = [
	{
		title: '路由名',
		dataIndex: 'name',
		key: 'name',
		width: 120,
		align: 'center',
	},
	{
		title: '接口权限',
		dataIndex: 'accessRequestList',
		key: 'accessRequestList',
		width: 150,
		align: 'center',
		ellipsis: true,
		customRender: ({ text: v, record }: { text: requestItem[] | undefined; record: routeTreeNode }) => {
			if (!record.component) return '无需授权'
			if (record.noNeedAuth) return '具有所有权限'
			if (v) {
				return v.map((i) => i.requestName).join(',')
			} else return ''
		},
	},
	{
		title: '按钮权限',
		dataIndex: 'accessActionList',
		key: 'accessActionList',
		width: 150,
		align: 'center',
		ellipsis: true,
		customRender: (scope:any) => {
			if (!scope.record.component) return '无需授权'
			if (scope.record.noNeedAuth) return '具有所有权限'
			const v:actionConfigType[]=scope.text
			if (v) {
				return v.map(i=>i.label).join(',')
			}
			else return ''
		},
	},
	{
		title: '操作',
		key: 'operation',
		fixed: 'right',
		align: 'center',
		width: 150,
	},
]
const emits = defineEmits(['close'])
const props = defineProps<{
	visible: boolean
	editRole: { [key: string]: any }
}>()
const tableData = ref<routeTreeNode[]>([])
const isSuccessOperate = ref(false)
const formInstance = ref<FormInstance | null>(null)
const roleItem = reactive({
	roleName: '',
})
const roleList = useRoleList()
const routeList = useRouteList()
const requestList = useRequestList()
const user = useUser()
const treeData = ref<routeTreeNode[]>([])
const expandedKeys = ref<string[]>([])
const checkedKeys = ref<string[]>([])
const halfCheckedKeys = ref<string[]>([])
const parentKeys=ref<string[]>([])
const giveAuthModalVisible = ref(false)
const editNode = ref({} as routeTreeNode)
const confirmLoading = ref(false)
const giveAuthModalTitle='页面内权限分配'

useModalDraggable(giveAuthModalVisible,giveAuthModalTitle)

const formLayout = {
	style: 'margin:10px',
	labelCol: { span: 6 },
	wrapperCol: { span: 18 },
	labelAlign: 'left',
}
const rowFormItemLayout = {
	labelCol: { span: 3 },
	wrapperCol: { span: 21 },
}
const rules = {
	roleName: [{ required: true, message: '请输入角色名！', trigger: 'change' }],
}

function showBack() {
	formInstance.value?.resetFields()
	nextTick(() => {
		checkedKeys.value = props.editRole.checkedIds.split(',')
		halfCheckedKeys.value = props.editRole.routeIds.split(',')
		const _tableData: routeTreeNode[] = []
		traverseTreeArr(JSON.parse(JSON.stringify(treeData.value)), (v: any) => {
			if (checkedKeys.value.includes(v.id)) _tableData.push(v)
		})
		// console.log(_tableData)
		tableData.value = _tableData.map((v) => {
			delete v.children
			return v
		})
		roleItem.roleName = props.editRole.roleName
	})
}

function getTreeData(list = routeList.list) {
	const {accessRequestIds,executeAction}=props.editRole
	let executeActionMap:any
		try {
			executeActionMap=JSON.parse(executeAction)
		} catch (error) {}
	parentKeys.value=[]
	const tree = listToTree<routeTreeNode>(list, 'id', 'pId', false, (node) => {
		const _requestList = requestList.list.filter((v) => v.routeIds?.includes(String(node.id)) || !v.needAuth)
		node.requestList = _requestList
		node.accessRequestList = _requestList.filter((v) => accessRequestIds.includes(String(v.id)))
		
		if(executeActionMap && executeActionMap[node.id]) 
		node.accessActionList=executeActionMap[node.id].split(',').map((k:actionKeyType)=>actionConfigMap[k])

		//if(!node.component && !node.link) parentKeys.value.push(node.id as string)
	}) as routeTreeNode
	traverseTreeArr([tree],(v)=>{
       if(v.children && v.children.length)  parentKeys.value.push(v.id)
  })
  treeData.value = sortTreeArr([tree],'rank')
	// console.log(tree)
}

function setExpendkey() {
	expandedKeys.value=[]
	routeList.list.forEach((v) => {
		expandedKeys.value.push(...props.editRole.routeIds.split(','))
	})
}

function handleTreeCheck(checkedKeys: string[], { checkedNodes, halfCheckedKeys: _halfCheckedKeys }: { checkedNodes: routeTreeNode[]; halfCheckedKeys: string[] }) {
	halfCheckedKeys.value = _halfCheckedKeys
	tableData.value = JSON.parse(JSON.stringify(checkedNodes)).map((v: routeTreeNode) => {
		if (v.children) {
			delete v.children
		}
		return v
	})
	// console.log(toRaw(tableData.value))
}
function handleGiveAuth(row: routeTreeNode) {
	editNode.value = row
	giveAuthModalVisible.value = true
}

function hanldeGiveAuthModalClose(auth:{accessRequestList:requestItem[],accessActionList:actionConfigType[]}){
  giveAuthModalVisible.value=false  
	if(!auth) return
	const {accessRequestList,accessActionList}=auth	
	if(accessRequestList) {
    traverseTreeArr(treeData.value,(v)=>{
        v.accessRequestList=accessRequestList
				v.accessActionList=accessActionList
    },'name',editNode.value.name,)
    tableData.value.forEach(v=>{
        if(v.name==editNode.value.name) {
					v.accessRequestList=accessRequestList
					v.accessActionList=accessActionList
				}
    })
  }
}

async function handleOk() {
	try {
		await formInstance.value?.validate()
		const creator = user.info.userName
		const createdTime = dayjs(Date.now()).format('YYYY-MM-DD HH:mm:ss')
		const checkedIds:string[]=[]
		checkedKeys.value.forEach((v)=>{
			if(parentKeys.value.includes(v))
			halfCheckedKeys.value.push(v)
			else
			checkedIds.push(v)
		})
		const routeIds=[...new Set([...checkedKeys.value,...halfCheckedKeys.value])]
		if (!routeIds.length) {
			message.warning('请勾选角色具备的路由(菜单)节点')
			return
		}

		const accessRequestIds = [
			...new Set(
				tableData.value
					.filter((v) => v.accessRequestList)
					.map((v) => v.accessRequestList?.map((i) => i.id))
					.flat()
			),
		].join(',')
		const executeActionMap:objType={}
        tableData.value.filter(v=>v.accessActionList).forEach(v=>executeActionMap[v.id]=v.accessActionList?.map(v=>v.value).join(','))
		const res = await roleList.updateItem({
			...props.editRole,
			roleName: roleItem.roleName,
			creator,
			createdTime,
			checkedIds:checkedIds.join(','),
			routeIds: routeIds.join(','),
			accessRequestIds,
			id: props.editRole.id,
			executeAction:JSON.stringify(executeActionMap)
		})
		if (res.code) {
			if ((res.code = 200)) {
				isSuccessOperate.value = true
				if(user.info.roleIds.includes(props.editRole.id))
			  emits('close', isSuccessOperate.value,props.editRole.id)
				else
				emits('close', isSuccessOperate.value)
			}
			if (res.code == 201) {
				message.error('角色名已存在！')
			}
		}
	} catch (error) {
		console.log(error)
	}
}

watch(
	() => props.visible,
	(nv) => {
		if (nv) {
			isSuccessOperate.value = false
			getTreeData()
			setExpendkey()
			showBack()
		}
	}
)
</script>

<template>
	<a-modal 
		:visible="visible"
		title="更新角色"
		:maskClosable="false"
		width="80%"
		centered
		:bodyStyle="{ maxHeight: $getModalBodyMaxHeight()+'px', overflow: 'auto' }"
		@ok="handleOk"
		@cancel="emits('close')"
		:confirmLoading="confirmLoading"
	>
		<a-row>
		
			<a-col :span="5" style="max-height: 580px; overflow: auto">
				<a-tree
					:fieldNames="{ children: 'children', title: 'title', key: 'id' }"
					v-model:expandedKeys="expandedKeys"
					v-model:checkedKeys="checkedKeys"
					:selectable="false"
					:treeData="treeData"
					checkable
					@check="handleTreeCheck"
				/>
			</a-col>
			<a-col :span="19" style="padding: 0 10px">
				<a-form :model="roleItem" :rules="rules" v-bind="formLayout" ref="formInstance" name="role_update">
					<a-row :gutter="[24, 8]">
						<a-col :span="12">
							<a-form-item name="roleName" label="角色名">
								<a-input v-model:value="roleItem.roleName" placeholder="角色名称必须唯一" allowClear />
							</a-form-item>
						</a-col>
					</a-row>
				</a-form>
				<a-table :dataSource="tableData" :columns="columns" size="small" style="width: 100%" rowKey="name" :scroll="{ x: '100%' }">
					<template #bodyCell="{ record, column }: any">
						<template v-if="column.key === 'operation'">
							<a-button type="primary" size="small" @click="handleGiveAuth(record)" :disabled="!record.component || record.noNeedAuth ? true : false">页面内权限分配</a-button>
						</template>
					</template>
				</a-table>
			</a-col>
		</a-row>

		<GiveAuth :visible="giveAuthModalVisible" :editNode="editNode" @close="hanldeGiveAuthModalClose" />
	</a-modal>
</template>
